package org.csource.pool;

import org.apache.commons.pool.PoolableObjectFactory;
import org.csource.fastdfs.*;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;

import java.io.IOException;

/**
 * Created with IntelliJ IDEA.
 * User: yangfei
 * Date: 2014/6/18
 * Time: 13:51
 * Desc:工厂类，用于处理验证，创建对象等方法
 */
public class FastDfsObjectFactory implements PoolableObjectFactory {

    private Logger log = LoggerFactory.getLogger(this.getClass());
    private String tracker_server;
    //HTTP访问服务的端口号
    private int httpPort;
    //连接超时的时限，单位为毫秒
    private int connectTimeout;
    //网络超时的时限，单位为毫秒
    private int networkTimeout;
    //非法访问屏蔽
    private Boolean Token;
    //字符集
    private String Charset;
    //加密
    private String secretKey;


    public FastDfsObjectFactory(String tracker_server,int httpPort,int connectTimeout,int networkTimeout,Boolean Token,String Charset,String secretKey) {
        log.debug("Tracker_server:"+tracker_server);
        log.debug("G_tracker_http_port:"+httpPort);
        log.debug("G_connect_timeout:"+connectTimeout);
        log.debug("G_network_timeout:"+networkTimeout);
        log.debug("G_anti_steal_token:"+Token);
        log.debug("G_charset:"+Charset);
        log.debug("G_secret_key:"+secretKey);

        this.tracker_server = tracker_server;
        this.httpPort = httpPort;
        this.connectTimeout = connectTimeout;
        this.networkTimeout = networkTimeout;
        this.Token = Token;
        this.Charset = Charset;
        this.secretKey = secretKey;
    }

    /**
     * 这里，在业务中第一次借对象的时候，这里要初始化一个，如果初始的都被借了，那就要继续初始
     * 这里创建的对象将被存到pool里面
     */
    @Override
    public Object makeObject() throws Exception {

        log.debug("FastDfsObjectFactory+makeObject:");
        String filename = null;
        //ip地址
        ClientGlobal.setG_tracker_server(this.tracker_server);
        //HTTP访问服务的端口号
        ClientGlobal.setG_tracker_http_port(this.httpPort);
        //连接超时的时限，单位为毫秒
        ClientGlobal.setG_connect_timeout(this.connectTimeout);
        //网络超时的时限，单位为毫秒
        ClientGlobal.setG_network_timeout(this.networkTimeout);
        ClientGlobal.setG_anti_steal_token(this.Token);
        //字符集
        ClientGlobal.setG_charset(this.Charset);
        //加密字符串
        ClientGlobal.setG_secret_key(this.secretKey);

        ClientGlobal.init(filename);

        TrackerClient tracker = new TrackerClient();
        StorageServer storageServer = null;
        TrackerServer trackerServer = tracker.getConnection();
        StorageClient client = new StorageClient(trackerServer, storageServer);
        return client;
    }

    /**
     * 这里我们销毁这个对象。不用这个对象了，这个方法得在业务使用过程中主动调用。
     * 在调用完这个方法过后，对象已经被销毁，但是在Object pool里面还是存在这个对象的
     * 只是这个对象是null而已。所以在调用完destroyObject过后，要记得把pool清空一下。
     */
    @Override
    public void destroyObject(Object o) throws Exception {
        log.debug("FastDfsObjectFactory+destroyObject:"+o);
        if ((o == null) || (!(o instanceof StorageClient)))
            return;
        StorageClient storageClient = (StorageClient)o;
        TrackerServer trackerServer = storageClient.getTrackerServer();
        StorageServer storageServer = storageClient.getStorageServer();
        trackerServer.close();
        storageServer.close();
    }

    /**
     *这个方法是验证对象，这里我们不做处理，这里在借对象和还对象的时候都要验证下的。
     */
    @Override
    public boolean validateObject(Object o) {
        log.debug("FastDfsObjectFactory+validateObject:"+o);
        StorageClient storageClient = (StorageClient)o;
        try
        {
            return ProtoCommon.activeTest(storageClient.trackerServer.getSocket());
        } catch (IOException e) {
            e.printStackTrace();
        }return false;
    }

    /**
     * 这里，我们在使用对象的时候，需要首先激活这个对象，但是在多线程情况下，
     * 这个对象已经被别的线程借去用了，那我们就要再建立一个对象。
     */
    @Override
    public void activateObject(Object o) throws Exception {
        log.debug("FastDfsObjectFactory+activateObject:"+o);
    }

    /**
     * 这里，在我们使用完每个对象过后，要做的就是归还，在归还后就要调用这个方法。
     * 简单的说，在还款凭证上面签个大名
     */
    @Override
    public void passivateObject(Object o) throws Exception {
        log.debug("FastDfsObjectFactory+passivateObject:"+o);
    }
}
